<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>defineProperty</title>
</head>
<body>
<script>
    /**
     *  Object.defineProperty()
     * 这个方法是给对象添加属性用的Object.defineProperty(需要添加属性的对象,需要添加的属性名,{配置项(例如value)}),默认添加的属性不能被枚举,修改,删除
     * 他与直接 需要添加属性的对象.需要添加的属性名=value不同的是,Object.defineProperty()添加的属性默认行为被限制
     * 如果想让Object.defineProperty()能够枚举,需要在配置项上面添加一个属性enumerable: true,想要让属性可以修改类似的添加一个属性writable:true...
     *
     *
     * 重点:
     *  get():每次访问添加的变量时,执行里边的函数,返回值赋值给被添加的值
     *  set(value):每次修改添加的变量时,执行里边的函数,修改得到的值会保存到value里
     *  get/set 方法不能与 value 和 writable 属性同时定义,因为他们之间互斥
     */


    let obj = {
        name: 'zyj',
        age: 18
    }
    //用之前的方法添加属性  加上这个之后能够遍历
    obj.sex = '男'
    console.log(Object.keys(obj))
    console.log('===================')
    //用Object.defineProperty()添加属性
    Object.defineProperty(obj, 'number', {value: '123'})
    console.log(Object.keys(obj))
    console.log('===================')
    //如果想让这个方法可枚举的话,可以在配置项上面添加一个属性  enumerable:true 默认值是false
    let number
    Object.defineProperty(obj, 'score', {
        // value: 98,
        enumerable: true,//设置属性可以被枚举,默认值是false
        // writable: true,//设置属性可以被修改,默认值是false
        configurable: true,//设置属性可以被删除,默认值是false


        //get 当有人读取添加的属性时,get函数就会被调用,返回值赋值给被添加的值
        get() {
            console.log('有人读取score属性了')
            return number //这样做的话,每次number改了值,我们去读取age属性时,他就会将age的值设置为number
        },

        //set 当有人修改了添加的属性值时,set函数就会被调用,且收到修改的具体值
        // 但是我们前面的get方法其实是将score的值设置成了number(每次访问score都会将number的值赋值给score)
        // 因此接受了值也不会发生改变
        set(value) {
            console.log('有人修改了score')
            number = value//将value的值赋值给number,当再次调用score时,我们就可以化将number的值返回给score
        }
    })
    console.log(Object.keys(obj))
</script>
</body>
</html>